﻿using NewLife.Net.Handlers;
using NewLife.Net;
using NewLife.Log;
using NewLife.Messaging;
using NewLife;
using NewLife.Serialization;
using System.IO;

namespace NetServer;

public class FileServer : NetServer<FileSession>
{
    public IList<String> Files { get; set; } = [];

    protected override void OnStart()
    {
        // 标准编码器不要返回内部数据包，而是直接返回消息对象，此时e.Message就是DefaultMessage
        Add(new StandardCodec { UserPacket = false });

        base.OnStart();
    }
}

public class FileSession : NetSession<FileServer>
{
    private MyFileInfo _info;
    private String _file;
    private Stream _target;

    protected override void OnReceive(ReceivedEventArgs e)
    {
        // 收到消息，识别文件头和文件内容
        if (e.Message is not DefaultMessage dm) return;

        // 借助Flag标记位区分消息类型，可用范围0~63。默认0是字符串，其它二进制
        var kind = (DataKinds)dm.Flag;
        switch (kind)
        {
            case DataKinds.String:
                var str = dm.Payload.ToStr();
                XTrace.WriteLine("收到：{0}", str);

                // 接受文件完成
                if (str.Contains("Finished"))
                {
                    _target.SetLength(_target.Position);
                    _target.TryDispose();
                    _target = null;

                    Host.Files.Add(_file);
                    Console.WriteLine(_file);
                }
                break;
            case DataKinds.Binary:
                break;
            case DataKinds.Json:
                // 开始创建文件
                _info = dm.Payload.ToStr().ToJsonEntity<MyFileInfo>();
                _file = $"D:\\ACCT\\logcenter\\LCSServer\\{_info.Name}"; ;
                //_file = _info.Name.GetFullPath();
                _target = new FileStream(_file, FileMode.OpenOrCreate, FileAccess.Write, FileShare.Read);
                break;
            case DataKinds.Packet:
            default:
                if (_target != null) dm.Payload.CopyTo(_target);
                break;
        }
    }
}

class MyFileInfo
{
    public String Name { get; set; }

    public Int64 Length { get; set; }

    public String MD5 { get; set; }
}
